// std::packaged_task测试
#include <deque>
#include <mutex>
#include <future>
#include <thread>
#include <utility>

std::mutex m;
// 任务队列
std::deque<std::packaged_task<void()>> tasks;

bool gui_shutdown_message_received();
bool get_and_process_gui_message();

void gui_thread() {
    // 循环接收一条关闭图形界面的信息
    while (!gui_shutdown_message_received())
    {
        get_and_process_gui_message(); // 处理
        // 轮询界面消息处理deque，当队列为空时一直查找
        std::packaged_task<void()> task;
        {
            std::lock_guard<std::mutex> lk(m);
            if (tasks.empty()) {
                continue;
            }
            // 取出任务，释放锁
            task = std::move(tasks.front());
            tasks.pop_front();
        }
        // 执行task
        task();
    }
}

std::thread gui_bg_thread(gui_thread);

// 提供一个打包好的任务
template<typename Func>
std::future<void> post_task_for_gui_thread(Func f)
{
    std::packaged_task<void()> task(f); 
    // 调用get_future成员函数获取期望值对象
    std::future<void> res = task.get_future(); 
    std::lock_guard<std::mutex> lk(m);
    // 将任务推入列表，期望值返回
    tasks.push_back(std::move(task));
    return res;
}
